/**************************************************************************************
*
*	Copyright (C) 2009 - 2012 Brent Andrew O. Chua - See LICENSE.txt for more info.
*		
*	Filename	-	XMLElement.h
*
*	Description -	
*
*	Comments	-	
*
*	Modification History:
*			Name			   Date					Description
*			MrCodeSushi	-	08/10/2011	-	Creation of this file
**************************************************************************************/
#ifndef _PSX_XML_NODE_H_
#define _PSX_XML_NODE_H_

#include "PulseSTD.h"
#include "String.h"
#include "SmartPointer.h"
#include "../External/tinyxml2/tinyxml2.h"

namespace Pulse
{
	class XMLElement
	{
	public:

		~XMLElement( void );

		BOOL IsValid( void ) const;

		String GetAttribute( const CHAR *pAttribute ) const;

		String GetAttribute( const Char *pAttribute ) const;

		String GetName( void ) const;

		String GetValue( void ) const;

		// NOTE: Returns the actual ASCII C-String buffer.
		//	this is very important for avoiding duplicating
		//	really big vertex/index string or just really huge strings
		//	in general.
		const Char * GetValueRaw( void ) const;

		// Returns null if it doesn't exist
		XMLElementPtr GetNextSibling( void ) const;

		// Returns null if it doesn't exist
		XMLElementPtr GetFirstChild( void ) const;

		// Returns null if it doesn't exist
		XMLElementPtr GetParent( void ) const;

		XMLDocumentPtr GetDocument( void ) { return m_pDoc; }

		// Used for writing
		////////////////////

		void SetName( const CHAR *pName );

		// NOTE: Changes the text content to the given pValue.
		void SetValue( const CHAR *pValue );

		// NOTE: Appends the text contained in this element.
		void AddValue( const CHAR *pValue );

		void SetAttribute( const CHAR *pName, const CHAR *pValue );

		void SetAttribute( const CHAR *pName, const INT value );

		void SetAttribute( const CHAR *pName, const UINT value );

		void SetAttribute( const CHAR *pName, const BOOL value );

		void SetAttribute( const CHAR *pName, const DOUBLE value );

		XMLElementPtr CreateChild( const CHAR *pName );

		void AttachChild( XMLElementPtr pElem );

		BOOL RemoveChild( const CHAR *pName );

		XMLElementPtr FindChild( const CHAR *pName );

		void ClearChildren( void );

	private:

		friend XMLParser;
		friend XMLDocument;

		XMLElement( void );

		XMLElement( XMLDocument *pDoc, tinyxml2::XMLElement *pElem );

		void AddChild( tinyxml2::XMLElement *pElement );

	private:

		// Document that owns this element. And yes i'm aware this using loose
		//	pointer. :)
		XMLDocument				*m_pDoc;
		tinyxml2::XMLElement	*m_pElem;
	};
}

#endif /* _PSX_XML_NODE_H_ */